package com.itheima.service.db.impl;

import cn.hutool.core.date.DateUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.itheima.domain.db.AnalysisByDay;
import com.itheima.mapper.AnalysisByDayMapper;
import com.itheima.mapper.LogMapper;
import com.itheima.service.db.AnalysisByDayService;
import com.itheima.util.ComputeUtil;
import com.itheima.vo.AnalysisSummaryVo;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.beans.factory.annotation.Autowired;

import java.math.BigDecimal;
import java.util.Date;

@DubboService
public class AnalysisByDayServiceImpl implements AnalysisByDayService {

    @Autowired
    private LogMapper logMapper;

    @Autowired
    private AnalysisByDayMapper analysisByDayMapper;

    @Override
    public void logToAnalysisByDay() {
        // 1.准备基础数据
        // 1-1 今天  2022-03-26
        String today = DateUtil.formatDate(new Date());
        // 1-2 昨天  2022-03-25
        String yesterday = DateUtil.offsetDay(new Date(), -1).toDateStr();

        // 2.查询log
        // 2-1 今日注册
        Integer regCount = logMapper.countRegAndLog(today, "0102");
        // 2-2 今日登录
        Integer logCount = logMapper.countRegAndLog(today, "0101");
        // 2-3 今日活跃
        Integer activeCount = logMapper.countActvie(today);
        // 2-4 次日留存
        Integer retention1dCount = logMapper.countRetention1d(today, yesterday);

        // 3.保存并封装
        LambdaQueryWrapper<AnalysisByDay> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(AnalysisByDay::getRecordDate, today);
        AnalysisByDay analysisByDay = analysisByDayMapper.selectOne(queryWrapper);
        if (analysisByDay == null) {  // 新增
            analysisByDay =  new AnalysisByDay();
            analysisByDay.setRecordDate(new Date()); // 统计日期
            analysisByDay.setNumRegistered(regCount); // 今日注册
            analysisByDay.setNumActive(activeCount);// 今日活跃
            analysisByDay.setNumLogin(logCount); // 今日登录
            analysisByDay.setNumRetention1d(retention1dCount);// 次日留存
            analysisByDayMapper.insert(analysisByDay);// insert语句
        } else { // 更新
            analysisByDay.setRecordDate(new Date()); // 统计日期
            analysisByDay.setNumRegistered(regCount); // 今日注册
            analysisByDay.setNumActive(activeCount);// 今日活跃
            analysisByDay.setNumLogin(logCount); // 今日登录
            analysisByDay.setNumRetention1d(retention1dCount);// 次日留存
            analysisByDayMapper.updateById(analysisByDay); // update语句
        }
    }

    @Override
    public AnalysisSummaryVo findAnalysisSummaryVo() {
        // 1.准备基础数据
        // 1-1 今天和昨天日期
        String today = DateUtil.offsetDay(new Date(), 0).toDateStr();
        String yesterday = DateUtil.offsetDay(new Date(), -1).toDateStr();
        // 1-2 前七天
        String weekday = DateUtil.offsetDay(new Date(), -7).toDateStr();
        // 1-3 前30天
        String monthday = DateUtil.offsetDay(new Date(), -30).toDateStr();
        // 1-4 今天分析
        AnalysisByDay todayAnalysis = analysisByDayMapper.findAnalysisByDay(today);
        // 1-5 昨天分析
        AnalysisByDay yesterdayAnalysis = analysisByDayMapper.findAnalysisByDay(yesterday);

        // 2.查询9份数据
        // 2-1 累计用户数
        Long cumulativeUsers = analysisByDayMapper.sumCumulativeUsers();
        // 2-2 过去30天活跃用户数
        Long activePassMonth = analysisByDayMapper.sumActivePass(monthday, today);
        // 2-3 过去7天活跃用户
        Long activePassWeek = analysisByDayMapper.sumActivePass(weekday, today);
        // 2-4 今日新增用户数量
        Integer newUsersToday = todayAnalysis.getNumRegistered();
        // 2-5 今日新增用户涨跌率，单位百分数，正数为涨，负数为跌   BigDecimal : 商业数字格式
        BigDecimal newUsersTodayRate = ComputeUtil.computeRate(newUsersToday, yesterdayAnalysis.getNumRegistered());
        // 2-6 今日登录次数
        Integer loginTimesToday = todayAnalysis.getNumLogin();
        // 2-7 今日登录次数涨跌率，单位百分数，正数为涨，负数为跌
        BigDecimal loginTimesTodayRate = ComputeUtil.computeRate(loginTimesToday, yesterdayAnalysis.getNumLogin());
        // 2-8 今日活跃用户数量
        Integer activeUsersToday = todayAnalysis.getNumActive();
        // 2-9 今日活跃用户涨跌率，单位百分数，正数为涨，负数为跌
        BigDecimal activeUsersTodayRate = ComputeUtil.computeRate(activeUsersToday, yesterdayAnalysis.getNumActive());
        // 3.封装并返回vo
        AnalysisSummaryVo vo = new AnalysisSummaryVo();
        vo.setCumulativeUsers(cumulativeUsers);
        vo.setActivePassMonth(activePassMonth);
        vo.setActivePassWeek(activePassWeek);
        vo.setNewUsersToday(newUsersToday.longValue());
        vo.setNewUsersTodayRate(newUsersTodayRate);
        vo.setLoginTimesToday(loginTimesToday.longValue());
        vo.setLoginTimesTodayRate(loginTimesTodayRate);
        vo.setActiveUsersToday(activeUsersToday.longValue());
        vo.setActiveUsersTodayRate(activeUsersTodayRate);

        return vo;
    }
}
